home *** CD-ROM | disk | FTP | other *** search
/ Resource Library: Multimedia / Resource Library: Multimedia.iso / maestro / source / unsupprt / guide / src / libguide / gio_path.c < prev    next >
Encoding:
C/C++ Source or Header  |  1993-06-15  |  5.3 KB  |  271 lines

  1. /*
  2.  * This file is a product of Sun Microsystems, Inc. and is provided for
  3.  * unrestricted use provided that this legend is included on all tape
  4.  * media and as a part of the software program in whole or part.  Users
  5.  * may copy or modify this file without charge, but are not authorized to
  6.  * license or distribute it to anyone else except as part of a product
  7.  * or program developed by the user.
  8.  * 
  9.  * THIS FILE IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE
  10.  * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR
  11.  * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE.
  12.  * 
  13.  * This file is provided with no support and without any obligation on the
  14.  * part of Sun Microsystems, Inc. to assist in its use, correction,
  15.  * modification or enhancement.
  16.  * 
  17.  * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
  18.  * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY THIS FILE
  19.  * OR ANY PART THEREOF.
  20.  * 
  21.  * In no event will Sun Microsystems, Inc. be liable for any lost revenue
  22.  * or profits or other special, indirect and consequential damages, even
  23.  * if Sun has been advised of the possibility of such damages.
  24.  * 
  25.  * Sun Microsystems, Inc.
  26.  * 2550 Garcia Avenue
  27.  * Mountain View, California  94043
  28.  */
  29.  
  30. #ifndef lint
  31. static char     sccsid[] = "@(#)gio_path.c    2.10 91/10/15 Copyright 1989 Sun Microsystems";
  32. #endif
  33.  
  34. #include <sys/param.h>
  35. #include <sys/types.h>
  36. #include <sys/stat.h>
  37. #include <pwd.h>
  38. #include <ctype.h>
  39. #include <errno.h>
  40. #include <string.h>
  41. #include "gio.h"
  42.  
  43. #define OK        0
  44. #define    ERROR        -1
  45.  
  46. /*
  47.  * Functions to manipulate file paths.
  48.  */
  49.  
  50. #define    GIL_SUFFIX    ".G"
  51. #define PROJ_SUFFIX    ".P"
  52.  
  53. /*
  54.  * Expand a path in place.  Returns OK if successful, otherwise sets errno
  55.  * and returns ERROR.
  56.  */
  57. int
  58. #ifdef __STDC__
  59. gio_expand_path(char *path)
  60. #else
  61. gio_expand_path(path)
  62.     char           *path;
  63. #endif
  64. {
  65.     void        expand_path();
  66.     char        buf[MAXPATHLEN];
  67.  
  68.     expand_path(path, buf);
  69.     strcpy(path, buf);
  70.     return OK;
  71. }
  72.  
  73. /*
  74.  * Expand a path to a GIL file in place.  Returns OK if successful, 
  75.  * otherwise sets errno and returns error.
  76.  */
  77. int
  78. #ifdef __STDC__
  79. gio_expand_gil_path(char *path)
  80. #else
  81. gio_expand_gil_path(path)
  82.     char           *path;
  83. #endif
  84. {
  85.     if (gio_expand_path(path) != OK)
  86.         return ERROR;
  87.  
  88.     if (gio_is_gil_path(path))
  89.         return OK;
  90.  
  91.     if (strlen(path) + strlen(GIL_SUFFIX) >= MAXPATHLEN) {
  92.         errno = ENAMETOOLONG;
  93.         return ERROR;
  94.     }
  95.  
  96.     strcat(path, GIL_SUFFIX);
  97.     return OK;
  98. }
  99.  
  100.  
  101. /*
  102.  * Expand a path to a project file in place.
  103.  */
  104. int
  105. #ifdef __STDC__
  106. gio_expand_proj_path(char *path)
  107. #else
  108. gio_expand_proj_path(path)
  109.     char    *path;
  110. #endif
  111. {
  112.     if (gio_expand_path(path) != 0)
  113.         return ERROR;
  114.  
  115.     if (gio_is_proj_path(path))
  116.         return OK;
  117.  
  118.     if (strlen(path) + strlen(PROJ_SUFFIX) >= MAXPATHLEN) {
  119.         errno = ENAMETOOLONG;
  120.         return ERROR;
  121.     }
  122.  
  123.     strcat(path, PROJ_SUFFIX);
  124.     return 0;
  125. }
  126.  
  127.  
  128. /*
  129.  * Return True if the given path ends with the gil suffix.
  130.  */
  131. int
  132. #ifdef __STDC__
  133. gio_is_gil_path(char *path)
  134. #else
  135. gio_is_gil_path(path)
  136.     char    *path;
  137. #endif
  138. {
  139.     return (strcmp(path + strlen(path) - strlen(GIL_SUFFIX),
  140.                GIL_SUFFIX) == 0);
  141. }
  142.  
  143.  
  144. /*
  145.  * Return True if the given path ends with the project suffix.
  146.  */
  147. int
  148. #ifdef __STDC__
  149. gio_is_proj_path(char *path)
  150. #else
  151. gio_is_proj_path(path)
  152.     char    *path;
  153. #endif
  154. {
  155.     return (strcmp(path + strlen(path) - strlen(PROJ_SUFFIX),
  156.                PROJ_SUFFIX) == 0);
  157. }
  158.  
  159.  
  160. /*
  161.  * expand_path from OpenWindows V2 FCS XView libraries
  162.  *
  163.  * Handles:
  164.  *    ~/ => home dir
  165.  *    ~user/ => user's home dir
  166.  *   If the environment variable a = "foo" and b = "bar" then:
  167.  *    $a    =>    foo
  168.  *    $a$b    =>    foobar
  169.  *    $a.c    =>    foo.c
  170.  *    xxx$a    =>    xxxfoo
  171.  *    ${a}!    =>    foo!
  172.  *    \$a    =>    \$a
  173.  *
  174.  * Arguments:
  175.  *    nm        input string
  176.  *    pathname    buffer to output expanded path
  177.  */
  178. void
  179. #ifdef __STDC__
  180. expand_path(char *nm, char *buf)
  181. #else
  182. expand_path(nm, buf)
  183.     char  *nm, *buf;
  184. #endif
  185. {
  186.     register char  *s, *d;
  187.     char            lnm[MAXPATHLEN];
  188.     int             q;
  189.     register char  *trimchars = "\n \t";
  190.     char           *getenv();
  191.  
  192.     /* Strip off leading & trailing whitespace and cr */
  193.     while (strchr(trimchars, *nm) != NULL)
  194.         nm++;
  195.     s = nm + (q = strlen(nm)) - 1;
  196.     while (q-- && strchr(trimchars, *s) != NULL)
  197.         *s = '\0';
  198.  
  199.     s = nm;
  200.     d = lnm;
  201.     q = nm[0] == '\\' && nm[1] == '~';
  202.  
  203.     /* Expand inline environment variables */
  204.     while (*d++ = *s)
  205.     {
  206.         if (*s == '\\') {
  207.             if (*(d - 1) = *++s)
  208.             {
  209.                 s++;
  210.                 continue;
  211.             } else
  212.                 break;
  213.         }
  214.         else if (*s++ == '$') {
  215.             register char  *start = d;
  216.             register        braces = *s == '{';
  217.             register char  *value;
  218.             while (*d++ = *s)
  219.                 if (braces ? *s == '}' : !isalnum(*s))
  220.                     break;
  221.                 else
  222.                     s++;
  223.             *--d = 0;
  224.             value = getenv(braces ? start + 1 : start);
  225.             if (value) {
  226.                 for (d = start - 1; *d++ = *value++;);
  227.                 d--;
  228.                 if (braces && *s)
  229.                     s++;
  230.             }
  231.         }
  232.     }
  233.  
  234.     /* Expand ~ and ~user */
  235.     nm = lnm;
  236.     s = "";
  237.     if (nm[0] == '~' && !q) { /* prefix ~ */
  238.         if (nm[1] == '/' || nm[1] == 0)
  239.         { /* ~/filename */
  240.             if (s = getenv("HOME"))
  241.             {
  242.                 if (*++nm)
  243.                     nm++;
  244.             }
  245.         }
  246.         else
  247.         {    /* ~user/filename */
  248.             register char  *nnm;
  249.             register struct passwd *pw;
  250.             for (s = nm; *s && *s != '/'; s++);
  251.             nnm = *s ? s + 1 : s;
  252.             *s = 0;
  253.             pw = (struct passwd *) getpwnam(nm + 1);
  254.             if (pw == 0) {
  255.                 *s = '/';
  256.                 s = "";
  257.             } else {
  258.                 nm = nnm;
  259.                 s = pw->pw_dir;
  260.             }
  261.         }
  262.     }
  263.     d = buf;
  264.     if (*s) {
  265.         while (*d++ = *s++);
  266.         *(d - 1) = '/';
  267.     }
  268.     s = nm;
  269.     while (*d++ = *s++);
  270. }
  271.